﻿using DSSDataServiceGenerator.Dialogs;
using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.Data;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Forms;
using System.Windows.Input;
using System.Xml.Linq;

namespace DSSDataServiceGenerator.ViewModel
{
    class MetadataViewModel
        : DependencyObject
    {
        public MetadataViewModel()
            : base()
        {
            this.PublishOutput = new ObservableCollection<Data.File>();
        }

        public static readonly DependencyProperty MetadataProperty = DependencyProperty.Register("Metadata", typeof(XElement), typeof(MetadataViewModel), new PropertyMetadata(null));
        public XElement Metadata
        {
            get { return (XElement)GetValue(MetadataProperty); }
            set { SetValue(MetadataProperty, value); }
        }

        private static string _PublishDirectory = "";

        private ICommand _PublishCommand = null;
        public ICommand PublishCommand
        {
            get
            {
                if (this._PublishCommand == null)
                {
                    this._PublishCommand = new Commands.ModelCommand(
                        (object parameter) =>
                        {
                            return true;//this.PublishOutput.Length != 0;
                        },
                        (object parameter) =>
                        {
                            FolderBrowserDialog saveFileDialog = new FolderBrowserDialog();

                            saveFileDialog.SelectedPath = _PublishDirectory;

                            saveFileDialog.Description = "Please select the project directory.";

                            if (saveFileDialog.ShowDialog() == DialogResult.OK)
                            {
                                _PublishDirectory = saveFileDialog.SelectedPath;

                                foreach (var item in this.PublishOutput)
                                {
                                    Directory.CreateDirectory(Path.GetDirectoryName(string.Concat(_PublishDirectory, item.Path)));

                                    File.WriteAllText(string.Concat(_PublishDirectory, item.Path), item.Content, Encoding.UTF8);
                                }

                                Process.Start(_PublishDirectory);

                                return;
                            }
                        }
                    );
                }

                return this._PublishCommand;
            }
        }

        private ICommand _GenerateCommand = null;
        public ICommand GenerateCommand
        {
            get
            {
                if (this._GenerateCommand == null)
                {
                    this._GenerateCommand = new Commands.ModelCommand(
                        (object parameter) =>
                        {
                            return true;//this.PublishOutput.Length != 0;
                        },
                        (object parameter) =>
                        {
                            this.PublishOutput.Clear();

                            Directory.EnumerateFiles("StyleSheets", "*.xslt").ToList().ForEach(
                                (string file) =>
                                {
                                    Transformation.CodeGenerator.Generate(file, this.Metadata)
                                    .ToList()
                                    .ForEach(
                                        (Data.File f) =>
                                        {
                                            this.PublishOutput.Add(f);
                                        }
                                    );
                                }
                            );
                        }
                    );
                }

                return this._GenerateCommand;
            }
        }

        public static readonly DependencyProperty PublishOutputProperty = DependencyProperty.Register("PublishOutput", typeof(ObservableCollection<Data.File>), typeof(MetadataViewModel), new PropertyMetadata(null));
        public ObservableCollection<Data.File> PublishOutput
        {
            get { return (ObservableCollection<Data.File>)GetValue(PublishOutputProperty); }
            set { SetValue(PublishOutputProperty, value); }
        }

        private ConnectionViewModel _ConnectionViewModel = null;
        public ConnectionViewModel ConnectionViewModel
        {
            get
            {
                if (this._ConnectionViewModel == null)

                    this._ConnectionViewModel = new ConnectionViewModel();

                return this._ConnectionViewModel;
            }
        }

        private ICommand _ConnectCommand = null;
        public ICommand ConnectCommand
        {
            get
            {
                if (this._ConnectCommand == null)
                {
                    this._ConnectCommand = new Commands.ModelCommand(
                        (object parameter) =>
                        {
                            return true;
                        },
                        (object parameter) =>
                        {
                            ConnectWindow connectWindow = new ConnectWindow(this.ConnectionViewModel);

                            if (connectWindow.ShowDialog() == true)

                                this.Metadata = connectWindow.ConnectionViewModel.SelectedConnection.GenerateMetadata();
                        }
                    );
                }

                return this._ConnectCommand;
            }
        }

        void Metadata_Changed(object sender, XObjectChangeEventArgs e)
        {
            if (this.GenerateCommand.CanExecute(null))

                this.GenerateCommand.Execute(null);
        }
    }
}
